package com.zlx.mall.basic.util.time;

import java.time.*;
import java.time.format.DateTimeFormatter;

/**
 * @author qingke
 **/
public abstract class MoreDateTimeUtil {

    public static final String SPACE = " ";

    public static final String DATE_FORMATTER_PATTERN = "yyyy-MM-dd";
    public static final DateTimeFormatter DATE_FORMATTER =
            DateTimeFormatter.ofPattern(DATE_FORMATTER_PATTERN);

    public static final String DATE_FORMATTER_PATTERN_SEPARATED_POINT = "yyyy.MM.dd";

    public static final DateTimeFormatter DATE_FORMATTER_PATTERN_SEPARATED_POINT_FORMATTER =
            DateTimeFormatter.ofPattern(DATE_FORMATTER_PATTERN_SEPARATED_POINT);

    public static final String TIME_FORMATTER_PATTERN = "HH:mm:ss";
    public static final DateTimeFormatter TIME_FORMATTER =
            DateTimeFormatter.ofPattern(TIME_FORMATTER_PATTERN);

    public static final String DATE_TIME_FORMATTER_PATTERN =
            DATE_FORMATTER_PATTERN.concat(SPACE).concat(TIME_FORMATTER_PATTERN);
    public static final DateTimeFormatter DATE_TIME_FORMATTER =
            DateTimeFormatter.ofPattern(DATE_TIME_FORMATTER_PATTERN);

    public static final String COMPACT_DATE_FORMATTER_PATTERN = "yyyyMMdd";
    public static final DateTimeFormatter COMPACT_DATE_FORMATTER =
            DateTimeFormatter.ofPattern(COMPACT_DATE_FORMATTER_PATTERN);

    public static final String COMPACT_TIME_FORMATTER_PATTERN = "HHmmss";
    public static final DateTimeFormatter COMPACT_TIME_FORMATTER =
            DateTimeFormatter.ofPattern(COMPACT_TIME_FORMATTER_PATTERN);

    public static final String COMPACT_DATE_TIME_FORMATTER_PATTERN = "yyyyMMddHHmmss";
    public static final DateTimeFormatter COMPACT_DATE_TIME_FORMATTER =
            DateTimeFormatter.ofPattern(COMPACT_DATE_TIME_FORMATTER_PATTERN);

    public static final ZoneId ZONE_CCT = ZoneId.of("Asia/Shanghai");

    private static final String ZERO_SECOND_CN = "0秒";
    private static final String ZERO_DAY_CN = "0天";
    private static final String UNIT_YEAR_CN = "年";
    private static final String UNIT_MONTH_CN = "月";
    private static final String UNIT_DAY_CN = "天";
    private static final String UNIT_HOUR_CN = "小时";
    private static final String UNIT_MINUTE_CN = "分钟";
    private static final String UNIT_SECOND_CN = "秒";

    public static final String FRIENDLY_TEXT_JUST_NOW_CN = "刚刚";
    public static final String FRIENDLY_TEXT_SECONDS_AGO_FORMAT_CN = "%d秒前";
    public static final String FRIENDLY_TEXT_MINUTE_AGO_FORMAT_CN = "%d分钟前";
    public static final DateTimeFormatter FRIENDLY_TEXT_TODAY_TIME_FORMAT_CN = DateTimeFormatter.ofPattern("今天HH:mm");
    public static final DateTimeFormatter FRIENDLY_TEXT_YESTERDAY_TIME_FORMAT_CN = DateTimeFormatter.ofPattern("昨天HH:mm");

    public static LocalTime parseTime(String text) {
        return LocalTime.parse(text, TIME_FORMATTER);
    }

    public static LocalTime parseCompactTime(String text) {
        return LocalTime.parse(text, COMPACT_TIME_FORMATTER);
    }

    public static LocalDate parseDate(String text) {
        return LocalDate.parse(text, DATE_FORMATTER);
    }

    public static LocalDate parseCompactDate(String text) {
        return LocalDate.parse(text, COMPACT_DATE_FORMATTER);
    }

    public static LocalDateTime parseDateTime(String text) {
        return LocalDateTime.parse(text, DATE_TIME_FORMATTER);
    }

    public static LocalDateTime parseCompactDateTime(String text) {
        return LocalDateTime.parse(text, COMPACT_DATE_TIME_FORMATTER);
    }

    public static String formatTime(LocalTime time) {
        return time.format(TIME_FORMATTER);
    }

    public static String formatCompactTime(LocalTime time) {
        return time.format(COMPACT_TIME_FORMATTER);
    }

    public static String formatDate(LocalDate date) {
        return date.format(DATE_FORMATTER);
    }

    public static String formatDateBySeparate(LocalDate date) {
        return date.format(DATE_FORMATTER_PATTERN_SEPARATED_POINT_FORMATTER);
    }


    public static String formatCompactDate(LocalDate date) {
        return date.format(COMPACT_DATE_FORMATTER);
    }

    public static String formatDateTime(LocalDateTime dateTime) {
        return dateTime.format(DATE_TIME_FORMATTER);
    }

    public static String formatCompactDateTime(LocalDateTime dateTime) {
        return dateTime.format(COMPACT_DATE_TIME_FORMATTER);
    }

    public static String formatBeforeDateTime(LocalDateTime before, LocalDateTime now) {

        Duration duration = Duration.between(before, now);
        if (duration.isNegative()) {
            // yyyy-MM-dd
            return before.format(DATE_FORMATTER);
        }

        long durationMillis = duration.toMillis();

        if (durationMillis < DateTimeUtil.MILLIS_PER_SECOND) {
            // 刚刚
            return FRIENDLY_TEXT_JUST_NOW_CN;
        } else if (durationMillis < DateTimeUtil.MILLIS_PER_MINUTE) {
            // 5秒前
            return String.format(FRIENDLY_TEXT_SECONDS_AGO_FORMAT_CN, duration.getSeconds());
        } else if (durationMillis < DateTimeUtil.MILLIS_PER_HOUR) {
            // 5分钟前
            return String.format(FRIENDLY_TEXT_MINUTE_AGO_FORMAT_CN, duration.toMinutes());
        }

        LocalDate today = now.toLocalDate();
        if (before.compareTo(LocalDateTime.of(today, LocalTime.MIN)) >= 0) {
            // 今天HH:mm
            return before.format(FRIENDLY_TEXT_TODAY_TIME_FORMAT_CN);
        } else if (before.compareTo(LocalDateTime.of(today.plusDays(-1), LocalTime.MIN)) >= 0) {
            // 昨天HH:mm
            return before.format(FRIENDLY_TEXT_YESTERDAY_TIME_FORMAT_CN);
        } else {
            // yyyy-MM-dd
            return before.format(DATE_FORMATTER);
        }
    }

    public static String formatBeforeDateTime(LocalDateTime before) {
        return formatBeforeDateTime(before, LocalDateTime.now());
    }

    public static String formatPeriod(Period period) {
        if (period.isZero()) {
            return ZERO_DAY_CN;
        } else {
            StringBuilder buf = new StringBuilder();
            if (period.getYears() != 0) {
                buf.append(period.getYears()).append(UNIT_YEAR_CN);
            }
            if (period.getMonths() != 0) {
                buf.append(period.getMonths()).append(UNIT_MONTH_CN);
            }
            if (period.getDays() != 0) {
                buf.append(period.getDays()).append(UNIT_DAY_CN);
            }
            return buf.toString();
        }
    }

    public static String formatDuration(Duration duration) {
        if (duration.isZero()) {
            return ZERO_SECOND_CN;
        }

        long seconds = duration.getSeconds();

        long hours = seconds / DateTimeUtil.SECONDS_PER_HOUR;
        int minutes = (int) ((seconds % DateTimeUtil.SECONDS_PER_HOUR) / DateTimeUtil.SECONDS_PER_MINUTE);
        int secs = (int) (seconds % DateTimeUtil.SECONDS_PER_MINUTE);

        StringBuilder buf = new StringBuilder();
        if (hours != 0) {
            buf.append(hours).append(UNIT_HOUR_CN);
        }
        if (minutes != 0) {
            buf.append(minutes).append(UNIT_MINUTE_CN);
        }
        if (secs != 0) {
            buf.append(secs).append(UNIT_SECOND_CN);
        }
        return buf.toString();
    }

    public static void main(String[] args) {

            /*System.out.println(Instant.now().toEpochMilli());
            System.out.println(LocalDateTime.ofInstant(Instant.now(), ZoneId.systemDefault()));
            System.out.println(LocalDateTime.ofInstant(Instant.now(), ZoneOffset.UTC));*/
        System.out.println(formatDateBySeparate(LocalDateTime.now().toLocalDate()));
    }

}
